package vip.xiaonuo.supplier.modular.business.businessMain.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollStreamUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson2.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import jakarta.annotation.Resource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
import vip.xiaonuo.common.enums.CommonSortOrderEnum;
import vip.xiaonuo.common.exception.CommonException;
import vip.xiaonuo.common.page.CommonPageRequest;
import vip.xiaonuo.supplier.modular.business.businessMain.entity.SupplierBusinessMain;
import vip.xiaonuo.supplier.modular.business.businessMain.mapper.SupplierBusinessMainMapper;
import vip.xiaonuo.supplier.modular.business.businessMain.param.SupplierBusinessMainAddParam;
import vip.xiaonuo.supplier.modular.business.businessMain.param.SupplierBusinessMainEditParam;
import vip.xiaonuo.supplier.modular.business.businessMain.param.SupplierBusinessMainIdParam;
import vip.xiaonuo.supplier.modular.business.businessMain.param.SupplierBusinessMainPageParam;
import vip.xiaonuo.supplier.modular.business.businessMain.service.SupplierBusinessMainService;
import vip.xiaonuo.supplier.modular.business.businessdetail.entity.SupplierBusinessDetail;
import vip.xiaonuo.supplier.modular.business.businessdetail.param.SupplierBusinessDetailAddParam;
import vip.xiaonuo.supplier.modular.business.businessdetail.service.SupplierBusinessDetailService;
import vip.xiaonuo.supplier.modular.business.businessdetail.service.impl.SupplierBusinessDetailServiceImpl;
import vip.xiaonuo.supplier.modular.custom.objects.entity.SupplierObjects;
import vip.xiaonuo.supplier.modular.custom.objects.mapper.SupplierObjectsMapper;
import vip.xiaonuo.supplier.modular.custom.objects.service.SupplierObjectsService;
import vip.xiaonuo.supplier.modular.finance.account.entity.SupplierAccount;
import vip.xiaonuo.supplier.modular.finance.account.mapper.SupplierAccountMapper;
import vip.xiaonuo.supplier.modular.finance.account.service.SupplierAccountService;
import vip.xiaonuo.supplier.modular.finance.balancelog.entity.SupplierBalanceLog;
import vip.xiaonuo.supplier.modular.finance.balancelog.service.SupplierBalanceLogService;
import vip.xiaonuo.supplier.modular.finance.settlement.service.SupplierSettlementService;
import vip.xiaonuo.supplier.modular.finance.settlementproject.entity.SupplierSettlementProject;
import vip.xiaonuo.supplier.modular.finance.settlementproject.service.SupplierSettlementProjectService;
import vip.xiaonuo.supplier.modular.warehouse.storesstream.entity.SupplierStoresStream;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * 业务主表Service接口实现类
 *
 * @author Mr.wu
 * @date  2025/03/26 11:03
 **/
@Service
public class SupplierBusinessMainServiceImpl extends ServiceImpl<SupplierBusinessMainMapper, SupplierBusinessMain> implements SupplierBusinessMainService {

    private static final SimpleDateFormat dateFormat = new SimpleDateFormat("yyyyMMddHHmmss");

    private static final AtomicInteger sequence = new AtomicInteger(0);

    private static String currentMinute = "";

    @Resource
    private SupplierBusinessDetailService supplierBusinessDetailService;

    @Resource
    private SupplierSettlementProjectService supplierSettlementProjectService;

    @Resource
    private SupplierAccountService supplierAccountService;

    @Autowired
    private SupplierObjectsMapper supplierObjectsMapper;

    @Resource
    private SupplierObjectsService supplierObjectsService;

    @Autowired
    private SupplierAccountMapper supplierAccountMapper;

    @Resource
    private SupplierBalanceLogService supplierBalanceLogService;

    @Override
    public Page<SupplierBusinessMain> page(SupplierBusinessMainPageParam supplierBusinessMainPageParam) {
        QueryWrapper<SupplierBusinessMain> queryWrapper = new QueryWrapper<SupplierBusinessMain>().checkSqlInjection();
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessType())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessType, supplierBusinessMainPageParam.getBusinessType());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessCode())) {
            queryWrapper.lambda().like(SupplierBusinessMain::getBusinessCode, supplierBusinessMainPageParam.getBusinessCode());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessObjectId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessObjectId, supplierBusinessMainPageParam.getBusinessObjectId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessHandlerId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessHandlerId, supplierBusinessMainPageParam.getBusinessHandlerId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessSalesmanId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessSalesmanId, supplierBusinessMainPageParam.getBusinessSalesmanId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessShippingStoreId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessShippingStoreId, supplierBusinessMainPageParam.getBusinessShippingStoreId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessShippingStorageId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessShippingStorageId, supplierBusinessMainPageParam.getBusinessShippingStorageId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessStorageStoreId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessStorageStoreId, supplierBusinessMainPageParam.getBusinessStorageStoreId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessCarrierId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessCarrierId, supplierBusinessMainPageParam.getBusinessCarrierId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessPaymentStatus())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessPaymentStatus, supplierBusinessMainPageParam.getBusinessPaymentStatus());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessStatus())){
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessStatus, supplierBusinessMainPageParam.getBusinessStatus());
        }
        //查询时间范围
        if (ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getStartCreateTime()) && ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getEndCreateTime())) {
            queryWrapper.lambda().between(SupplierBusinessMain::getCreateTime, supplierBusinessMainPageParam.getStartCreateTime() + " 00:00:01", supplierBusinessMainPageParam.getEndCreateTime() + " 23:59:59");
        }
        //数据归属
        queryWrapper.lambda().eq(SupplierBusinessMain::getCompanyId, StpLoginUserUtil.getLoginUser().getCompanyId());
        if(ObjectUtil.isAllNotEmpty(supplierBusinessMainPageParam.getSortField(), supplierBusinessMainPageParam.getSortOrder())) {
            CommonSortOrderEnum.validate(supplierBusinessMainPageParam.getSortOrder());
            queryWrapper.orderBy(true, supplierBusinessMainPageParam.getSortOrder().equals(CommonSortOrderEnum.ASC.getValue()),
                    StrUtil.toUnderlineCase(supplierBusinessMainPageParam.getSortField()));
        } else {
            queryWrapper.lambda().orderByDesc(SupplierBusinessMain::getId);
        }
        return this.page(CommonPageRequest.defaultPage(), queryWrapper);
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public SupplierBusinessMain add(JSONObject supplierBusinessJson) {
        SupplierBusinessMain supplierBusinessMain = BeanUtil.toBean(supplierBusinessJson, SupplierBusinessMain.class);
        //数据归属
        supplierBusinessMain.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());
        //单据编号
        Date now = new Date();
        String datePortion = dateFormat.format(now);
        int sequenceNumber = 1;
        if (datePortion.equals(currentMinute)) {
            sequenceNumber = sequence.incrementAndGet();
            if (sequenceNumber > 999) {
                sequence.set(0);
                sequenceNumber = 1;
            }
        } else {
            sequence.set(1);
            currentMinute = datePortion;
        }
        supplierBusinessMain.setBusinessCode(supplierBusinessMain.getBusinessType() + datePortion + String.format("%03d", sequenceNumber));

        //在这里要判断业务主表类型，作出相应的处理
        String type = null;
        switch (supplierBusinessMain.getBusinessType()) {
            case "EN": //采购入库
                type = "01";
                break;
            case "RS": //销售退货
                type = "02";
                break;
            case "SO": //销售出库
                type = "05";
                break;
            case "RE": //采购退货
                type = "06";
                break;
            default:
                break;
        }
        if(ObjectUtil.isNotEmpty(type)) {
            //查找采购支出的项目
            List<SupplierSettlementProject> projects = supplierSettlementProjectService.list(new LambdaQueryWrapper<SupplierSettlementProject>().eq(SupplierSettlementProject::getCompanyId, StpLoginUserUtil.getLoginUser().getCompanyId()).eq(SupplierSettlementProject::getProjectCode, type));
            if (ObjectUtil.isNotEmpty(projects)) {
                supplierBusinessMain.setBusinessProjectId(projects.get(0).getId());//结算项目：采购支出
            }
        }

        //默认未支付状态
        supplierBusinessMain.setBusinessPaymentStatus("0");
        //如果是直接审核过账的，执行审核过账动作动作。
        if (supplierBusinessMain.getBusinessStatus().equals("1")){
            //1、根据付款金额，填写支付状态
            if(supplierBusinessMain.getBusinessSettlementType().equals("0")){
                if((supplierBusinessMain.getBusinessInAmount().compareTo(BigDecimal.ZERO))==0) { //实付金额为0，未付
                    supplierBusinessMain.setBusinessPaymentStatus("0");
                } else {
                    if((supplierBusinessMain.getBusinessInAmount().compareTo(supplierBusinessMain.getBusinessReceivableAmount()))==0) { //实付金额待于应付金额，则已付
                        supplierBusinessMain.setBusinessPaymentStatus("1");
                    }else{//部分支付
                        supplierBusinessMain.setBusinessPaymentStatus("2");
                    }
                }
            }
            if(supplierBusinessMain.getBusinessSettlementType().equals("1")){
                if((supplierBusinessMain.getBusinessPayAmount().compareTo(BigDecimal.ZERO))==0) { //实付金额为0，未付
                    supplierBusinessMain.setBusinessPaymentStatus("0");
                } else {
                    if((supplierBusinessMain.getBusinessPayAmount().compareTo(supplierBusinessMain.getBusinessPayableAmount()))==0) { //实付金额待于应付金额，则已付
                        supplierBusinessMain.setBusinessPaymentStatus("1");
                    }else{//部分支付
                        supplierBusinessMain.setBusinessPaymentStatus("2");
                    }
                }
            }

        }
        this.save(supplierBusinessMain);
        //保存后，再处理结算账户和结算对象
        if (supplierBusinessMain.getBusinessStatus().equals("1")){
            //1.2有收付款行为，更新结算账户结算前余额和结算后余额
            if((!supplierBusinessMain.getBusinessPaymentStatus().equals("0")) && ObjectUtil.isNotEmpty(supplierBusinessMain.getBusinessAccountId())){
                SupplierAccount supplierAccount = supplierAccountService.queryEntity(supplierBusinessMain.getBusinessAccountId());
                if(ObjectUtil.isNotEmpty(supplierAccount)){
                    //写账户变动日志
                    SupplierBalanceLog supplierBalanceLog = new SupplierBalanceLog();
                    supplierBalanceLog.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());
                    supplierBalanceLog.setLogType("0");//结算账户日志
                    supplierBalanceLog.setLogAccountId(supplierAccount.getId());
                    supplierBalanceLog.setLogBalanceBefore(supplierAccount.getAccountBalance());
                    supplierBalanceLog.setLogBusinessId(supplierBusinessMain.getId());
                    supplierBalanceLog.setLogBusinessCode(supplierBusinessMain.getBusinessCode());
                    if(supplierBusinessMain.getBusinessSettlementType().equals("0")) {//收款
                        supplierBalanceLog.setLogInAmount(supplierBusinessMain.getBusinessInAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierAccount.getAccountBalance().add(supplierBusinessMain.getBusinessInAmount()));
                        supplierBalanceLog.setLogAbstract("余额增加，收入" + supplierBusinessMain.getBusinessInAmount() + "元，审核过账单据-" + supplierBusinessMain.getBusinessCode() + supplierBusinessMain.getBusinessAbstract());//摘要
                    }else{
                        supplierBalanceLog.setLogPayAmount(supplierBusinessMain.getBusinessPayAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierAccount.getAccountBalance().subtract(supplierBusinessMain.getBusinessPayAmount()));
                        supplierBalanceLog.setLogAbstract("余额减少，支付" + supplierBusinessMain.getBusinessPayAmount() + "元，审核过账单据-" + supplierBusinessMain.getBusinessCode() + supplierBusinessMain.getBusinessAbstract());//摘要
                    }
                    supplierBalanceLogService.save(supplierBalanceLog);
                    //1.3更新收款账户余额
                    UpdateWrapper<SupplierAccount> supplierAccountUpdateWrapper = new UpdateWrapper<>();
                    supplierAccountUpdateWrapper.eq("id",supplierBusinessMain.getBusinessAccountId()).setSql("`ACCOUNT_BALANCE`=`ACCOUNT_BALANCE` + " + (supplierBusinessMain.getBusinessSettlementType().equals("0") ? (supplierBusinessMain.getBusinessInAmount()) : (BigDecimal.ZERO.subtract(supplierBusinessMain.getBusinessPayAmount()))) );
                    supplierAccountMapper.update(null, supplierAccountUpdateWrapper);
                }
            }
            //2、如果未结清，则对业务对象的应收应付做出处理
            if((!supplierBusinessMain.getBusinessPaymentStatus().equals("1")) && ObjectUtil.isNotEmpty(supplierBusinessMain.getBusinessObjectId())){//如果是未结算或部分结算的
                SupplierObjects supplierObjects = supplierObjectsService.queryEntity(supplierBusinessMain.getBusinessObjectId());
                if(ObjectUtil.isNotEmpty(supplierObjects)) {
                    SupplierBalanceLog supplierBalanceLog = new SupplierBalanceLog();
                    supplierBalanceLog.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());
                    supplierBalanceLog.setLogType("1");//结算对象应收应付日志
                    supplierBalanceLog.setLogAccountId(supplierObjects.getId());
                    supplierBalanceLog.setLogBalanceBefore(supplierObjects.getObjectAccountsPayable());
                    supplierBalanceLog.setLogBusinessId(supplierBusinessMain.getId());
                    supplierBalanceLog.setLogBusinessCode(supplierBusinessMain.getBusinessCode());
                    if(supplierBusinessMain.getBusinessSettlementType().equals("0")) {//收款
                        supplierBalanceLog.setLogInAmount(supplierBusinessMain.getBusinessPendingInAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierObjects.getObjectAccountsPayable().subtract(supplierBusinessMain.getBusinessPendingInAmount()));
                        supplierBalanceLog.setLogAbstract("应收增加" + supplierBusinessMain.getBusinessPendingInAmount() + "元,审核过账单据-"+ supplierBusinessMain.getBusinessCode() +"," + supplierBusinessMain.getBusinessAbstract());//摘要
                    }else{
                        supplierBalanceLog.setLogPayAmount(supplierBusinessMain.getBusinessPendingPayAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierObjects.getObjectAccountsPayable().add(supplierBusinessMain.getBusinessPendingPayAmount()));
                        supplierBalanceLog.setLogAbstract("应付增加" + supplierBusinessMain.getBusinessPendingPayAmount() + "元,审核过账单据-"+ supplierBusinessMain.getBusinessCode() +"," + supplierBusinessMain.getBusinessAbstract());//摘要
                    }
                    supplierBalanceLogService.save(supplierBalanceLog);
                    //2.1、处理业务主表中的业务对象结算前应收应付与结算后的应收应付
                    UpdateWrapper<SupplierObjects> supplierObjectsUpdateWrapper = new UpdateWrapper<>();
                    supplierObjectsUpdateWrapper.eq("id",supplierBusinessMain.getBusinessObjectId()).setSql("`OBJECT_ACCOUNTS_PAYABLE`=`OBJECT_ACCOUNTS_PAYABLE` + " + (supplierBusinessMain.getBusinessSettlementType().equals("0") ? (BigDecimal.ZERO.subtract(supplierBusinessMain.getBusinessPendingInAmount())) : supplierBusinessMain.getBusinessPendingPayAmount()));
                    supplierObjectsMapper.update(null, supplierObjectsUpdateWrapper);
                }
            }
        }
        //处理明细数据
        List<LinkedHashMap> supplierBusinessDetailLinkHasMap = (List<LinkedHashMap>) supplierBusinessJson.get("details");
        List<SupplierBusinessDetail> supplierBusinessDetailList = new ArrayList<>();
        supplierBusinessDetailLinkHasMap.forEach((LinkedHashMap detailLinkedHashMap) ->{
            SupplierBusinessDetail supplierBusinessDetail = BeanUtil.toBean(detailLinkedHashMap,SupplierBusinessDetail.class);
            supplierBusinessDetail.setDetailBusinessId(supplierBusinessMain.getId()); //主业务ID
            supplierBusinessDetail.setDetailStorageStorage(supplierBusinessMain.getBusinessStorageStoreId()); //入库仓库
            supplierBusinessDetail.setDetailShippingStorage(supplierBusinessMain.getBusinessShippingStoreId()); //出库仓库
            supplierBusinessDetail.setDetailStatus(supplierBusinessMain.getBusinessStatus());//订单状态
            supplierBusinessDetail.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());//数据归属
            supplierBusinessDetailList.add(supplierBusinessDetail);
        });
        supplierBusinessDetailService.saveOrUpdateDetail(null,supplierBusinessMain,supplierBusinessDetailList);
        return supplierBusinessMain;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public SupplierBusinessMain edit(JSONObject supplierBusinessJson) {
        SupplierBusinessMain supplierBusinessMain = BeanUtil.toBean(supplierBusinessJson, SupplierBusinessMain.class);
        SupplierBusinessMain supplierBusinessMainNew = this.queryEntity(supplierBusinessMain.getId());
        SupplierBusinessMain supplierBusinessMainOld = new SupplierBusinessMain();
        supplierBusinessMainOld.setBusinessStatus(supplierBusinessMainNew.getBusinessStatus());
        BeanUtil.copyProperties(supplierBusinessMain, supplierBusinessMainNew);
        if(supplierBusinessMainOld.getBusinessStatus().equals("1") && supplierBusinessMainNew.getBusinessStatus().equals("1")){
            throw new CommonException("业务单据已审核过账，不能修改！");
        }

        //如果原单据为空（说明是直接审核过账的）或原单据状态为草稿，新单据为过账（此为审核过账动作）则执行审核过账动作。
        if (supplierBusinessMainNew.getBusinessStatus().equals("1") && supplierBusinessMainOld.getBusinessStatus().equals("0")){
            //1、根据付款金额，填写支付状态
            if(supplierBusinessMainNew.getBusinessSettlementType().equals("0")){
                if((supplierBusinessMainNew.getBusinessInAmount().compareTo(BigDecimal.ZERO))==0) { //实付金额为0，未付
                    supplierBusinessMainNew.setBusinessPaymentStatus("0");
                } else {
                    if((supplierBusinessMainNew.getBusinessInAmount().compareTo(supplierBusinessMainNew.getBusinessReceivableAmount()))==0) { //实付金额待于应付金额，则已付
                        supplierBusinessMainNew.setBusinessPaymentStatus("1");
                    }else{//部分支付
                        supplierBusinessMainNew.setBusinessPaymentStatus("2");
                    }
                }
            }
            if(supplierBusinessMainNew.getBusinessSettlementType().equals("1")){
                if((supplierBusinessMainNew.getBusinessPayAmount().compareTo(BigDecimal.ZERO))==0) { //实付金额为0，未付
                    supplierBusinessMainNew.setBusinessPaymentStatus("0");
                } else {
                    if((supplierBusinessMainNew.getBusinessPayAmount().compareTo(supplierBusinessMainNew.getBusinessPayableAmount()))==0) { //实付金额待于应付金额，则已付
                        supplierBusinessMainNew.setBusinessPaymentStatus("1");
                    }else{//部分支付
                        supplierBusinessMainNew.setBusinessPaymentStatus("2");
                    }
                }
            }
            //有付款行为，且结算账户不为空
            if((!supplierBusinessMainNew.getBusinessPaymentStatus().equals("0")) && ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessAccountId())){
                //1.1更新支付前余额和支付后余额
                SupplierAccount supplierAccount = supplierAccountService.queryEntity(supplierBusinessMain.getBusinessAccountId());
                if(ObjectUtil.isNotEmpty(supplierAccount)){
                    //写账户变动日志
                    SupplierBalanceLog supplierBalanceLog = new SupplierBalanceLog();
                    supplierBalanceLog.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());
                    supplierBalanceLog.setLogType("0");//结算账户日志
                    supplierBalanceLog.setLogAccountId(supplierAccount.getId());
                    supplierBalanceLog.setLogBalanceBefore(supplierAccount.getAccountBalance());
                    supplierBalanceLog.setLogBusinessId(supplierBusinessMainNew.getId());
                    supplierBalanceLog.setLogBusinessCode(supplierBusinessMainNew.getBusinessCode());
                    if(supplierBusinessMainNew.getBusinessSettlementType().equals("0")) {//收款
                        supplierBalanceLog.setLogInAmount(supplierBusinessMainNew.getBusinessInAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierAccount.getAccountBalance().add(supplierBusinessMainNew.getBusinessInAmount()));
                        supplierBalanceLog.setLogAbstract("余额增加，收入" + supplierBusinessMainNew.getBusinessInAmount() + "元,审核过账单据-"+ supplierBusinessMainNew.getBusinessCode() +"," + supplierBusinessMainNew.getBusinessAbstract());//摘要
                    }else{
                        supplierBalanceLog.setLogPayAmount(supplierBusinessMainNew.getBusinessPayAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierAccount.getAccountBalance().subtract(supplierBusinessMainNew.getBusinessPayAmount()));
                        supplierBalanceLog.setLogAbstract("余额减少，支付" + supplierBusinessMainNew.getBusinessPayAmount() + "元,审核过账单据-"+ supplierBusinessMainNew.getBusinessCode() +"," + supplierBusinessMainNew.getBusinessAbstract());//摘要
                    }
                    supplierBalanceLogService.save(supplierBalanceLog);
                    UpdateWrapper<SupplierAccount> supplierAccountUpdateWrapper = new UpdateWrapper<>();
                    supplierAccountUpdateWrapper.eq("id",supplierBusinessMainNew.getBusinessAccountId()).setSql("`ACCOUNT_BALANCE`=`ACCOUNT_BALANCE` + " + (supplierBusinessMainNew.getBusinessSettlementType().equals("0") ? (supplierBusinessMainNew.getBusinessInAmount()) : (BigDecimal.ZERO.subtract(supplierBusinessMainNew.getBusinessPayAmount()))) );
                    supplierAccountMapper.update(null, supplierAccountUpdateWrapper);
                }

            }

            //2、处理与业务对象相关的（结算前余额与结算后余额，并更新其应收应传
            if((!supplierBusinessMainNew.getBusinessPaymentStatus().equals("1")) && ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessObjectId())){ //如果是未结算或部分结算的
                SupplierObjects supplierObjects = supplierObjectsService.queryEntity(supplierBusinessMainNew.getBusinessObjectId());
                if(ObjectUtil.isNotEmpty(supplierObjects)) {
                    //2.1、写结算对象应收应付日志
                    SupplierBalanceLog supplierBalanceLog = new SupplierBalanceLog();
                    supplierBalanceLog.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());
                    supplierBalanceLog.setLogType("1");//结算对象应收应付日志
                    supplierBalanceLog.setLogAccountId(supplierObjects.getId());
                    supplierBalanceLog.setLogBalanceBefore(supplierObjects.getObjectAccountsPayable());
                    supplierBalanceLog.setLogBusinessId(supplierBusinessMainNew.getId());
                    supplierBalanceLog.setLogBusinessCode(supplierBusinessMainNew.getBusinessCode());
                    if(supplierBusinessMainNew.getBusinessSettlementType().equals("0")) {//收款
                        supplierBalanceLog.setLogInAmount(supplierBusinessMainNew.getBusinessPendingInAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierObjects.getObjectAccountsPayable().subtract(supplierBusinessMainNew.getBusinessPendingInAmount()));
                        supplierBalanceLog.setLogAbstract((supplierBusinessMainNew.getBusinessType().equals("RS") ? "应付减少" : "应收增加") + supplierBusinessMainNew.getBusinessPendingInAmount() + "元,审核过账单据-"+ supplierBusinessMainNew.getBusinessCode() +"," +supplierBusinessMainNew.getBusinessAbstract());//摘要
                    }else{
                        supplierBalanceLog.setLogPayAmount(supplierBusinessMainNew.getBusinessPendingPayAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierObjects.getObjectAccountsPayable().add(supplierBusinessMainNew.getBusinessPendingPayAmount()));
                        supplierBalanceLog.setLogAbstract( (supplierBusinessMainNew.getBusinessType().equals("RE") ? "应收减少" : "应付增加") + supplierBusinessMainNew.getBusinessPendingPayAmount() + "元,审核过账单据-"+ supplierBusinessMainNew.getBusinessCode() +"," +supplierBusinessMainNew.getBusinessAbstract());//摘要
                    }
                    supplierBalanceLogService.save(supplierBalanceLog);
                    //2.2、处理业务对象的总应收应付
                    UpdateWrapper<SupplierObjects> supplierObjectsUpdateWrapper = new UpdateWrapper<>();
                    supplierObjectsUpdateWrapper.eq("id",supplierBusinessMainNew.getBusinessObjectId()).setSql("`OBJECT_ACCOUNTS_PAYABLE`=`OBJECT_ACCOUNTS_PAYABLE` + " + (supplierBusinessMainNew.getBusinessSettlementType().equals("0") ? (BigDecimal.ZERO.subtract(supplierBusinessMainNew.getBusinessPendingInAmount())) : supplierBusinessMainNew.getBusinessPendingPayAmount()));
                    supplierObjectsMapper.update(null, supplierObjectsUpdateWrapper);
                }
            }
        }
        //以上是审核的主业务表流程
        //如果原来单据是审核，改为草稿状态（反审核）业务流程
        if (supplierBusinessMainNew.getBusinessStatus().equals("0") && supplierBusinessMainOld.getBusinessStatus().equals("1")){
            //不管这前是否结算，都要处理业务对象的应收或应付，如果是已结算，需要把结算的钱退到账户中，如果是未结算，则需要把应收或应付减掉
            if(ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessObjectId()) && ((ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessReceivableAmount()) && ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessInAmount()) && (supplierBusinessMainNew.getBusinessReceivableAmount().subtract(supplierBusinessMainNew.getBusinessInAmount())).compareTo(BigDecimal.ZERO)>0) || (ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessPayableAmount()) && ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessPayAmount()) && (supplierBusinessMainNew.getBusinessPayableAmount().subtract(supplierBusinessMainNew.getBusinessPayAmount())).compareTo(BigDecimal.ZERO)>0) )) {
                SupplierObjects supplierObjects = supplierObjectsService.queryEntity(supplierBusinessMainNew.getBusinessObjectId());
                if(ObjectUtil.isNotEmpty(supplierObjects)) {
                    //写结算对象应收应付日志
                    SupplierBalanceLog supplierBalanceLog = new SupplierBalanceLog();
                    supplierBalanceLog.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());

                    supplierBalanceLog.setLogType("1");//结算对象应收应付日志
                    supplierBalanceLog.setLogAccountId(supplierObjects.getId());
                    supplierBalanceLog.setLogBalanceBefore(supplierObjects.getObjectAccountsPayable());
                    supplierBalanceLog.setLogBusinessId(supplierBusinessMainNew.getId());
                    supplierBalanceLog.setLogBusinessCode(supplierBusinessMainNew.getBusinessCode());
                    if (supplierBusinessMainNew.getBusinessSettlementType().equals("0")) {//收款
                        supplierBalanceLog.setLogInAmount(BigDecimal.ZERO.subtract(supplierBusinessMainNew.getBusinessReceivableAmount().subtract(supplierBusinessMainNew.getBusinessInAmount())));
                        supplierBalanceLog.setLogBalanceAfter(supplierObjects.getObjectAccountsPayable().add(supplierBusinessMainNew.getBusinessReceivableAmount().subtract(supplierBusinessMainNew.getBusinessInAmount())));
                        supplierBalanceLog.setLogAbstract((supplierBusinessMainNew.getBusinessType().equals("RS") ? "应付增加" : "应收减少") + supplierBusinessMainNew.getBusinessReceivableAmount().subtract(supplierBusinessMainNew.getBusinessInAmount()) + "元,反审核单据-"+ supplierBusinessMainNew.getBusinessCode() +"," +supplierBusinessMainNew.getBusinessAbstract());//摘要
                    } else {
                        supplierBalanceLog.setLogPayAmount(BigDecimal.ZERO.subtract(supplierBusinessMainNew.getBusinessPayableAmount().subtract(supplierBusinessMainNew.getBusinessPayAmount())));
                        supplierBalanceLog.setLogBalanceAfter(supplierObjects.getObjectAccountsPayable().subtract(supplierBusinessMainNew.getBusinessPayableAmount().subtract(supplierBusinessMainNew.getBusinessPayAmount())));
                        supplierBalanceLog.setLogAbstract((supplierBusinessMainNew.getBusinessType().equals("RE") ? "应收增加" : "应付减少") + supplierBusinessMainNew.getBusinessPayableAmount().subtract(supplierBusinessMainNew.getBusinessPayAmount()) + "元,反审核单据-"+ supplierBusinessMainNew.getBusinessCode() +"," +supplierBusinessMainNew.getBusinessAbstract());//摘要
                    }
                    supplierBalanceLogService.save(supplierBalanceLog);
                    UpdateWrapper<SupplierObjects> supplierObjectsUpdateWrapper = new UpdateWrapper<>();
                    supplierObjectsUpdateWrapper.eq("id", supplierBusinessMainNew.getBusinessObjectId()).setSql("`OBJECT_ACCOUNTS_PAYABLE`=`OBJECT_ACCOUNTS_PAYABLE` + " + (supplierBusinessMainNew.getBusinessSettlementType().equals("0") ? supplierBusinessMainNew.getBusinessReceivableAmount().subtract(supplierBusinessMainNew.getBusinessInAmount()) : (BigDecimal.ZERO.subtract(supplierBusinessMainNew.getBusinessPayableAmount().subtract(supplierBusinessMainNew.getBusinessPayAmount())))));
                    supplierObjectsMapper.update(null, supplierObjectsUpdateWrapper);
                }
            }
            //如果是已结算或部分结算，就是说我方账户已收到钱或付过钱，需要反向操作回来
            if((!supplierBusinessMainNew.getBusinessPaymentStatus().equals("0")) && ObjectUtil.isNotEmpty(supplierBusinessMainNew.getBusinessAccountId()) && (supplierBusinessMainNew.getBusinessInAmount().compareTo(BigDecimal.ZERO)>0 || supplierBusinessMainNew.getBusinessPayAmount().compareTo(BigDecimal.ZERO)>0)){
                supplierBusinessMainNew.setBusinessAccountBalanceBefore(BigDecimal.ZERO);
                supplierBusinessMainNew.setBusinessAccountBalanceAfter(BigDecimal.ZERO);
                SupplierAccount supplierAccount = supplierAccountService.queryEntity(supplierBusinessMain.getBusinessAccountId());
                if(ObjectUtil.isNotEmpty(supplierAccount)) {
                    SupplierBalanceLog supplierBalanceLog = new SupplierBalanceLog();
                    supplierBalanceLog.setCompanyId(StpLoginUserUtil.getLoginUser().getCompanyId());
                    supplierBalanceLog.setLogAbstract(supplierBusinessMainNew.getBusinessAbstract());//摘要
                    supplierBalanceLog.setLogType("0");//结算账户日志
                    supplierBalanceLog.setLogAccountId(supplierAccount.getId());
                    supplierBalanceLog.setLogBalanceBefore(supplierAccount.getAccountBalance());
                    supplierBalanceLog.setLogBusinessId(supplierBusinessMainNew.getId());
                    supplierBalanceLog.setLogBusinessCode(supplierBusinessMainNew.getBusinessCode());
                    if(supplierBusinessMainNew.getBusinessSettlementType().equals("0")) {//收款
                        supplierBalanceLog.setLogInAmount(supplierBusinessMainNew.getBusinessInAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierAccount.getAccountBalance().subtract(supplierBusinessMainNew.getBusinessInAmount()));
                        supplierBalanceLog.setLogAbstract("余额减少" + supplierBusinessMainNew.getBusinessInAmount() + "元，单据反审核-" + supplierBusinessMainNew.getBusinessCode() + supplierBusinessMainNew.getBusinessAbstract());//摘要
                    }else{
                        supplierBalanceLog.setLogPayAmount(supplierBusinessMainNew.getBusinessPayAmount());
                        supplierBalanceLog.setLogBalanceAfter(supplierAccount.getAccountBalance().add(supplierBusinessMainNew.getBusinessPayAmount()));
                        supplierBalanceLog.setLogAbstract("余额增加" + supplierBusinessMainNew.getBusinessPayAmount() + "元，单据反审核-" + supplierBusinessMainNew.getBusinessCode() + supplierBusinessMainNew.getBusinessAbstract());//摘要
                    }
                    supplierBalanceLogService.save(supplierBalanceLog);
                    UpdateWrapper<SupplierAccount> supplierAccountUpdateWrapper = new UpdateWrapper<>();
                    supplierAccountUpdateWrapper.eq("id",supplierBusinessMain.getBusinessAccountId()).setSql("`ACCOUNT_BALANCE`=`ACCOUNT_BALANCE` + " + (supplierBusinessMainNew.getBusinessSettlementType().equals("0") ? (BigDecimal.ZERO.subtract(supplierBusinessMainNew.getBusinessInAmount())) : supplierBusinessMainNew.getBusinessPayAmount()));
                    supplierAccountMapper.update(null, supplierAccountUpdateWrapper);
                }
            }
            //反审核时，支付状态为未支付
            supplierBusinessMainNew.setBusinessPaymentStatus("0");
        }
        //以上是反审核的主业务表流程
        this.updateById(supplierBusinessMainNew);
        List<LinkedHashMap> supplierBusinessDetailLinkHasMap = (List<LinkedHashMap>) supplierBusinessJson.get("details");
        List<SupplierBusinessDetail> supplierBusinessDetailList = new ArrayList<>();
        List<String> detailIds = new ArrayList<>();
        supplierBusinessDetailLinkHasMap.forEach((LinkedHashMap detailLinkedHashMap) ->{
            SupplierBusinessDetail supplierBusinessDetail = BeanUtil.toBean(detailLinkedHashMap,SupplierBusinessDetail.class);
            supplierBusinessDetail.setDetailBusinessId(supplierBusinessMainNew.getId()); //主业务ID
            supplierBusinessDetail.setDetailStorageStorage(supplierBusinessMainNew.getBusinessStorageStoreId()); //入库仓库
            supplierBusinessDetail.setDetailShippingStorage(supplierBusinessMainNew.getBusinessShippingStoreId()); //出库仓库
            supplierBusinessDetail.setDetailStatus(supplierBusinessMainNew.getBusinessStatus());//订单状态
            supplierBusinessDetailList.add(supplierBusinessDetail);
            detailIds.add(supplierBusinessDetail.getId());//如果发生删除明细行，这里是需要保留的数据
        });
        //保存或更新明细表
        supplierBusinessDetailService.saveOrUpdateDetail(supplierBusinessMainOld, supplierBusinessMainNew,supplierBusinessDetailList);
        return supplierBusinessMainNew;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public void delete(List<SupplierBusinessMainIdParam> supplierBusinessMainIdParamList) {
        //要删除明细数据
        List<SupplierBusinessMain> supplierBusinessMainList = this.list(new LambdaQueryWrapper<SupplierBusinessMain>().eq(SupplierBusinessMain::getBusinessStatus,'1').in(SupplierBusinessMain::getId,CollStreamUtil.toList(supplierBusinessMainIdParamList, SupplierBusinessMainIdParam::getId)));
        if(ObjectUtil.isNotEmpty(supplierBusinessMainList)) {
            throw new CommonException("业务状态为已审核，不能删除！业务单号为：{}", CollStreamUtil.toList(supplierBusinessMainList, SupplierBusinessMain::getBusinessCode).toString());
        }
        List<SupplierBusinessDetail> supplierBusinessDetailList = supplierBusinessDetailService.list(new LambdaQueryWrapper<SupplierBusinessDetail>().in(SupplierBusinessDetail::getDetailBusinessId,CollStreamUtil.toList(supplierBusinessMainIdParamList, SupplierBusinessMainIdParam::getId)));
        if(ObjectUtil.isNotEmpty(supplierBusinessDetailList)) {
            supplierBusinessDetailService.removeByIds(supplierBusinessDetailList);
        }
        // 执行删除
        this.removeByIds(CollStreamUtil.toList(supplierBusinessMainIdParamList, SupplierBusinessMainIdParam::getId));
    }

    @Override
    public SupplierBusinessMain detail(SupplierBusinessMainIdParam supplierBusinessMainIdParam) {
        return this.queryEntity(supplierBusinessMainIdParam.getId());
    }

    @Override
    public SupplierBusinessMain queryEntity(String id) {
        SupplierBusinessMain supplierBusinessMain = this.getById(id);
        if(ObjectUtil.isEmpty(supplierBusinessMain)) {
            throw new CommonException("业务主表不存在，id值为：{}", id);
        }
        return supplierBusinessMain;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public void cancel(List<SupplierBusinessMainIdParam> supplierBusinessMainIdParamList) {
        //要作废的明细数据
        List<SupplierBusinessMain> supplierBusinessMainList = this.list(new LambdaQueryWrapper<SupplierBusinessMain>().eq(SupplierBusinessMain::getBusinessStatus,'1').in(SupplierBusinessMain::getId,CollStreamUtil.toList(supplierBusinessMainIdParamList, SupplierBusinessMainIdParam::getId)));
        if(ObjectUtil.isNotEmpty(supplierBusinessMainList)) {
            throw new CommonException("业务单据已审核，不能作废！业务单号为：{}", CollStreamUtil.toList(supplierBusinessMainList, SupplierBusinessMain::getBusinessCode).toString());
        }
        //业务明细作废
        UpdateWrapper<SupplierBusinessDetail> supplierBusinessDetailUpdateWrapper = new UpdateWrapper<>();
        supplierBusinessDetailUpdateWrapper.in("detail_business_id",CollStreamUtil.toList(supplierBusinessMainIdParamList, SupplierBusinessMainIdParam::getId)).setSql("`DETAIL_STATUS`= '2'" );
        supplierBusinessDetailService.update(null, supplierBusinessDetailUpdateWrapper);
        // 执行主业务单作废
        UpdateWrapper<SupplierBusinessMain> supplierBusinessMainUpdateWrapper = new UpdateWrapper<>();
        supplierBusinessMainUpdateWrapper.in("id",CollStreamUtil.toList(supplierBusinessMainIdParamList, SupplierBusinessMainIdParam::getId)).setSql("`BUSINESS_STATUS`= '2'" );
        this.update(null, supplierBusinessMainUpdateWrapper);
    }

    @Override
    public Page<SupplierBusinessMain> pendingPage(SupplierBusinessMainPageParam supplierBusinessMainPageParam) {
        QueryWrapper<SupplierBusinessMain> queryWrapper = new QueryWrapper<SupplierBusinessMain>().checkSqlInjection();
        //业务类型
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessType())) {
            queryWrapper.lambda().in(SupplierBusinessMain::getBusinessType, supplierBusinessMainPageParam.getBusinessType().split(","));
        }
        //业务单号
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessCode())) {
            queryWrapper.lambda().like(SupplierBusinessMain::getBusinessCode, supplierBusinessMainPageParam.getBusinessCode());
        }
        //结算对象
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessObjectId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessObjectId, supplierBusinessMainPageParam.getBusinessObjectId());
        }
        //经手人
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessHandlerId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessHandlerId, supplierBusinessMainPageParam.getBusinessHandlerId());
        }
        //业务员
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessSalesmanId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessSalesmanId, supplierBusinessMainPageParam.getBusinessSalesmanId());
        }
        //业务门店
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessShippingStoreId())) {
            queryWrapper.lambda().and(i -> i.eq(SupplierBusinessMain::getBusinessShippingStoreId, supplierBusinessMainPageParam.getBusinessShippingStoreId()).or().eq(SupplierBusinessMain::getBusinessStorageStoreId, supplierBusinessMainPageParam.getBusinessShippingStoreId()));
        }
        //业务仓库
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessShippingStorageId())) {
            queryWrapper.lambda().and(i->i.eq(SupplierBusinessMain::getBusinessShippingStorageId, supplierBusinessMainPageParam.getBusinessShippingStorageId()).or().eq(SupplierBusinessMain::getBusinessStorageStorageId, supplierBusinessMainPageParam.getBusinessShippingStorageId()));
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessStorageStoreId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessStorageStoreId, supplierBusinessMainPageParam.getBusinessStorageStoreId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessCarrierId())) {
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessCarrierId, supplierBusinessMainPageParam.getBusinessCarrierId());
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessPaymentStatus())) {
            queryWrapper.lambda().in(SupplierBusinessMain::getBusinessPaymentStatus, supplierBusinessMainPageParam.getBusinessPaymentStatus().split(","));
        }
        if(ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getBusinessStatus())){
            queryWrapper.lambda().eq(SupplierBusinessMain::getBusinessStatus, supplierBusinessMainPageParam.getBusinessStatus());
        }
        //查询时间范围
        if (ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getStartCreateTime()) && ObjectUtil.isNotEmpty(supplierBusinessMainPageParam.getEndCreateTime())) {
            queryWrapper.lambda().between(SupplierBusinessMain::getCreateTime, supplierBusinessMainPageParam.getStartCreateTime() + " 00:00:01", supplierBusinessMainPageParam.getEndCreateTime() + " 23:59:59");
        }
        //数据归属
        queryWrapper.lambda().eq(SupplierBusinessMain::getCompanyId, StpLoginUserUtil.getLoginUser().getCompanyId());
        if(ObjectUtil.isAllNotEmpty(supplierBusinessMainPageParam.getSortField(), supplierBusinessMainPageParam.getSortOrder())) {
            CommonSortOrderEnum.validate(supplierBusinessMainPageParam.getSortOrder());
            queryWrapper.orderBy(true, supplierBusinessMainPageParam.getSortOrder().equals(CommonSortOrderEnum.ASC.getValue()),
                    StrUtil.toUnderlineCase(supplierBusinessMainPageParam.getSortField()));
        } else {
            queryWrapper.lambda().orderByAsc(SupplierBusinessMain::getId);
        }
        return this.page(CommonPageRequest.defaultPage(), queryWrapper);
    }
}
